Skip to content

Domainmapping bring your own certificate#11250

Merged
knative-prow-robot merged 19 commits intoknative:mainfrom
leetcope:tls-byo-certificate
Jun 2, 2021
Merged

Domainmapping bring your own certificate#11250
knative-prow-robot merged 19 commits intoknative:mainfrom
leetcope:tls-byo-certificate

Conversation

@leetcope
Copy link
Contributor

Allow domainmappings to specify the tls secret to be used by the autoTLS
certificate

These changes assume that autoTLS is enabled in the cluster and that if the secret doesn't exist in the cluster the intent
is to create a new secret with the given name

Fixes #10530

Release Note

Domainmapping can now specify a tls secret to be used as the https certificate

@google-cla google-cla bot added the cla: yes Indicates the PR's author has signed the CLA. label Apr 22, 2021
@knative-prow-robot knative-prow-robot added area/API API objects and controllers area/networking size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Apr 22, 2021
@codecov
Copy link

codecov bot commented Apr 22, 2021

Codecov Report

Merging #11250 (7461340) into main (3676663) will increase coverage by 0.01%.
The diff coverage is 80.00%.

Impacted file tree graph

@@            Coverage Diff             @@
##             main   #11250      +/-   ##
==========================================
+ Coverage   87.70%   87.71%   +0.01%     
==========================================
  Files         191      191              
  Lines        9246     9256      +10     
==========================================
+ Hits         8109     8119      +10     
  Misses        882      882              
  Partials      255      255              
Impacted Files Coverage Δ
...g/apis/serving/v1alpha1/domainmapping_lifecycle.go 81.81% <0.00%> (-3.90%) ⬇️
pkg/apis/serving/v1alpha1/domainmapping_types.go 100.00% <ø> (ø)
pkg/reconciler/domainmapping/reconciler.go 92.10% <100.00%> (+0.43%) ⬆️
pkg/activator/net/revision_backends.go 92.41% <0.00%> (+0.89%) ⬆️

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 3676663...7461340. Read the comment docs.

Copy link
Contributor

@julz julz left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks good, thanks! 🎉 I mostly just have a little bike-shed about the field name :).

I guess (probably in a follow up, no need for it to be done in this PR, as far as I'm concerned) we will want to relax the check in the reconciler to allow tls even with autoTLS disabled as long as (and only as long as!) the secret is provided explicitly.

// If defined it will use the existing tls secret with the given name, otherwise it will attempt to create
// a new secret with the expected name to be used by the certificate.
// +optional
TLSSecret string `json:"tlsSecret,omitempty"`
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you think about having this roughly match the similar section in K8s Ingress? (Mostly just for consistency/familiarity). That would also line up with (Knative) IngressTLS which has secretName.

i.e.

tls:
  secretName: ..

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@julz I've addressed your comments please let me know if everything looks good to you

@leetcope leetcope force-pushed the tls-byo-certificate branch from c8517ae to 6a26305 Compare April 24, 2021 05:53
@knative-prow-robot knative-prow-robot added size/L Denotes a PR that changes 100-499 lines, ignoring generated files. and removed size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Apr 24, 2021
@leetcope leetcope force-pushed the tls-byo-certificate branch 2 times, most recently from 4e8d58c to 082a31e Compare April 24, 2021 06:21
@leetcope
Copy link
Contributor Author

leetcope commented May 3, 2021

/retest

@leetcope
Copy link
Contributor Author

leetcope commented May 3, 2021

/assign @dprotaso

Copy link
Contributor

@julz julz left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Couple little comments


func (r *Reconciler) tls(ctx context.Context, dm *v1alpha1.DomainMapping) ([]netv1alpha1.IngressTLS, []netv1alpha1.HTTP01Challenge, error) {
if !autoTLSEnabled(ctx, dm) {
if !autoTLSEnabled(ctx, dm) && dm.Spec.TLS == nil {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd actually land this line in a follow-on PR I think: we want to think through the cases here (eg if autotls is not enabled and spec.TLS is non-nil but SecretName is empty what should happen? Should we error out if the cert doesn't exist but autotls is disabled?) and probably add some test coverage.

type SecretTLS struct {
// SecretName is the name of a TLS secret.
//
// Either a existing secret in the cluster or the new secret to be created.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
// Either a existing secret in the cluster or the new secret to be created.
// Either an existing secret in the cluster or the new secret to be created.

Spec: networkingv1alpha1.CertificateSpec{
DNSNames: []string{dnsName},
SecretName: certName,
SecretName: secretName,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The godoc for this says

SecretName is the name of the secret resource to store the SSL certificate in.

It's not obvious whether different controllers will check this secret and not overwrite it. Even if it does not what happens when the certificate in the secret expires?

I wonder if when we bring your own certificate we don't use the default certificate class.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wonder if when we bring your own certificate we don't use the default certificate class.

I guess we still need something to set the certificate as 'ready`

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

At least in net-http01 I see it checks for the secret before trying to create it here which is consistent with what I've tested, this also happens with cert-manager but I haven't found the specific code that does this in cert-manager. I'm not sure if this answers your question

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

net-http01 may be work well but we can't assume other's won't

ie. cert manager

The secret name is delegated to a cert manager CRD here. A rough scan looks like there are edge cases where it might fail

Specifically the secret is evaluated against the following policy chain to determine whether to re-issue the certificate

Two concerning assertions are:

SecretPrivateKeyMatchesSpec

When creating the cert manager crd we don't indicate the private key type. When it's not set cert manager assumes we're bringing a RSA private key. Thus if we brought a ECDSA cert then I think it trigger a reissue that'll fail/overwrite our secret

SecretIssuerAnnotationsNotUpToDate

it seems like the secret needs the 'correct' annotations or it'll be re-issued - these annotations are cert manager specific.

@knative-prow-robot knative-prow-robot added size/M Denotes a PR that changes 30-99 lines, ignoring generated files. and removed size/L Denotes a PR that changes 100-499 lines, ignoring generated files. labels May 6, 2021
@leetcope leetcope force-pushed the tls-byo-certificate branch from b48d735 to e4b5958 Compare May 6, 2021 04:06
@dprotaso
Copy link
Member

dprotaso commented May 6, 2021

/retest

@dprotaso
Copy link
Member

dprotaso commented May 6, 2021

Can we add an e2e test?

<td>
<em>(Optional)</em>
<p>TLS indicates the existing or expected tls secret that should be used for certificate generation.</p>
<p>If defined it will use the existing tls secret with the given name, otherwise it will attempt to create
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same comment as below

<td>
<em>(Optional)</em>
<p>TLS indicates the existing or expected tls secret that should be used for certificate generation.</p>
<p>If defined it will use the existing tls secret with the given name, otherwise it will attempt to create
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same comment as below

// TLS indicates the existing or expected tls secret that should be used for certificate generation.
//
// If defined it will use the existing tls secret with the given name, otherwise it will attempt to create
// a new secret with the expected name to be used by the certificate.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this still true ? As in will a new secret be created if one doesnt exist ?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might also want to update the description in the PR and original issue if the requirements have changed as we explicitly don't want to create a secret if it doesn't exist

@knative-prow-robot knative-prow-robot added size/XXL Denotes a PR that changes 1000+ lines, ignoring generated files. area/test-and-release It flags unit/e2e/conformance/perf test issues for product features and removed size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels May 18, 2021
@leetcope leetcope force-pushed the tls-byo-certificate branch from 5acb2a9 to 670109a Compare May 18, 2021 05:09
@knative-prow-robot knative-prow-robot added size/L Denotes a PR that changes 100-499 lines, ignoring generated files. and removed size/XXL Denotes a PR that changes 1000+ lines, ignoring generated files. labels May 18, 2021
Comment on lines +75 to +76
// SecretName is the name of a TLS secret.
//
// An existing tls secret.
SecretName string `json:"secretName"`
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
// SecretName is the name of a TLS secret.
//
// An existing tls secret.
SecretName string `json:"secretName"`
// SecretName is the name of the existing secret used to terminate TLS traffic.
SecretName string `json:"secretName"`

Comment on lines +79 to +81
// SecretNamespace is the namespace of the existing TLS secret.
//
// Namespace of the existing secret, if missing the namespace of the domainmapping is assumed.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
// SecretNamespace is the namespace of the existing TLS secret.
//
// Namespace of the existing secret, if missing the namespace of the domainmapping is assumed.
// SecretNamespace is the namespace of the existing secret used to terminate SSL traffic. If empty the namespace of the DomainMapping is assumed.

Comment on lines +98 to +101
// TLS indicates the existing tls secret that should be used for this domain.
//
// If defined it will use the tls secret with the given name assumed to exist
// in the same namespace as the domainmapping.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
// TLS indicates the existing tls secret that should be used for this domain.
//
// If defined it will use the tls secret with the given name assumed to exist
// in the same namespace as the domainmapping.
// TLS allows the DomainMapping to terminate TLS traffic with an existing secret.

Comment on lines +186 to +213
if dm.Spec.TLS != nil {
namespace := dm.Namespace
if dm.Spec.TLS.SecretNamespace != "" {
namespace = dm.Spec.TLS.SecretNamespace
}
return []netv1alpha1.IngressTLS{
{
Hosts: []string{dm.Name},
SecretName: dm.Spec.TLS.SecretName,
SecretNamespace: namespace,
},
}, nil, nil
}

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you add a unit test for this as well?

}, metav1.CreateOptions{})

if err != nil {
t.Fatalf("Domainmapping creation could not be completed: %v", err)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: update this message to say the secret failed to create

Status: v1alpha1.DomainMappingStatus{},
}

t.Log("HOST===>", host)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

unsure if this was for debugging - can we change the message to be a clear sentence or drop it?

t.Log("HOST===>", host)
_, err = clients.ServingAlphaClient.DomainMappings.Create(context.Background(), &dm, metav1.CreateOptions{})
if err != nil {
t.Fatalf("Problem creating domainmapping : %v", err)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's print the host here

Suggested change
t.Fatalf("Problem creating domainmapping : %v", err)
t.Fatalf("Problem creating DomainMapping %q: %v", host, err)

Comment on lines +235 to +257
if waitErr := wait.PollImmediate(test.PollInterval, test.PollTimeout, func() (bool, error) {
ingresses, err := clients.NetworkingClient.Ingresses.Get(context.Background(), ksvc.Service.Name, metav1.GetOptions{})
if err != nil {
return false, err
}
for _, cond := range ingresses.Status.Conditions {
if cond.Type == apis.ConditionReady {
return cond.IsTrue(), nil
}
}
return false, nil
}); waitErr != nil {
t.Fatalf("Ingresses %s never became ready: %v", ksvc.Service.Name, waitErr)
}

err = shared.CheckDistribution(context.Background(), t, clients,
&url.URL{
Host: host,
Scheme: "HTTPS",
}, 1, 1, []string{test.PizzaPlanetText1}, resolvableCustomDomain)
if err != nil {
t.Fatalf("Hitting %v didn't return the expected response: %v", dm.Name, err)
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The Kingress is sorta an implementation detail of the DomainMapping - we should be checking the Ready condition on the DomainMapping itself

I also wonder if we CheckDistribution isn't needed and maybe we could just use WaitForEndpointState

@leetcope leetcope force-pushed the tls-byo-certificate branch from 56aac5f to b14642a Compare May 21, 2021 17:31
leetcope and others added 13 commits June 1, 2021 14:30
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
allow domainmappings to specify the tls secret to be used by the autoTLS
certificate

Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Co-authored-by: Bishoy Youssef <byoussef@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Co-authored-by: Bishoy Youssef <byoussef@vmware.com>
Co-authored-by: Bishoy Youssef <byoussef@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Co-authored-by: Sameer Vohra <vsameer@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Signed-off-by: Fabian Lopez <lfabian@vmware.com>
@leetcope leetcope force-pushed the tls-byo-certificate branch from 90ab26a to ba2fd25 Compare June 1, 2021 20:07
@dprotaso
Copy link
Member

dprotaso commented Jun 2, 2021

/approve 🎉

leaving lgtm to @julz

@knative-prow-robot knative-prow-robot added the approved Indicates a PR has been approved by an approver from all required OWNERS files. label Jun 2, 2021
Copy link
Contributor

@julz julz left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Awesome stuff, thanks! Couple little indentation nits and then it'll lgtm 🔥

Comment on lines +205 to +212
return []netv1alpha1.IngressTLS{
{
Hosts: []string{dm.Name},
SecretName: dm.Spec.TLS.SecretName,
SecretNamespace: dm.Namespace,
},
}, nil, nil
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

indentation nit:

Suggested change
return []netv1alpha1.IngressTLS{
{
Hosts: []string{dm.Name},
SecretName: dm.Spec.TLS.SecretName,
SecretNamespace: dm.Namespace,
},
}, nil, nil
}
return []netv1alpha1.IngressTLS{{
Hosts: []string{dm.Name},
SecretName: dm.Spec.TLS.SecretName,
SecretNamespace: dm.Namespace,
}}, nil, nil
}

}

host := ksvc.Service.Name + ".example.org"
// set resolvabledomain for custom domain to false by default.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: not sure this comment really adds anything the code it's describing doesn't say more clearly, I'd probably just drop it

Name: ksvc.Service.Name,
Namespace: ksvc.Service.Namespace,
Kind: "Service",
}, TLS: &v1alpha1.SecretTLS{
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
}, TLS: &v1alpha1.SecretTLS{
},
TLS: &v1alpha1.SecretTLS{

Comment on lines +66 to +67

// service to be mapped
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd be tempted to drop this comment since it doesn't really add anything, but if we keep it let's capitalise it and add a period just to be consistent with most of the rest of the code in serving.

Suggested change
// service to be mapped
// Create service to be mapped.

Signed-off-by: Fabian Lopez <lfabian@vmware.com>
Copy link
Contributor

@julz julz left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

/lgtm
/approve

🥳🥳🥳

@knative-prow-robot knative-prow-robot added the lgtm Indicates that a PR is ready to be merged. label Jun 2, 2021
@knative-prow-robot
Copy link
Contributor

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: dprotaso, julz, shinigambit

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@knative-prow-robot
Copy link
Contributor

knative-prow-robot commented Jun 2, 2021

@shinigambit: The following tests failed, say /retest to rerun all failed tests:

Test name Commit Details Rerun command
pull-knative-serving-contour-tls 5acb2a9 link /test pull-knative-serving-contour-tls
pull-knative-serving-kourier-stable-tls 5acb2a9 link /test pull-knative-serving-kourier-stable-tls
pull-knative-serving-istio-stable-mesh-tls 5acb2a9 link /test pull-knative-serving-istio-stable-mesh-tls

Full PR test history. Your PR dashboard.

Details

Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository. I understand the commands that are listed here.

@leetcope
Copy link
Contributor Author

leetcope commented Jun 2, 2021

/retest

@knative-prow-robot knative-prow-robot merged commit f2cb8e5 into knative:main Jun 2, 2021
@nak3
Copy link
Contributor

nak3 commented Jul 30, 2021

It seems no documentation is available yet. I opened knative/docs#4081 to track for the new docs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

approved Indicates a PR has been approved by an approver from all required OWNERS files. area/API API objects and controllers area/networking area/test-and-release It flags unit/e2e/conformance/perf test issues for product features cla: yes Indicates the PR's author has signed the CLA. lgtm Indicates that a PR is ready to be merged. size/L Denotes a PR that changes 100-499 lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

DomainMapping to allow BYO certificate

6 participants